FairCalendarController.get   C
last analyzed

Complexity

Conditions 7

Size

Total Lines 94
Code Lines 80

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 80
dl 0
loc 94
rs 6.2545
c 0
b 0
f 0
cc 7

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
import {
2
  Controller,
3
  Get,
4
  Inject,
5
  Query,
6
  Render,
7
  Req,
8
  UseGuards
9
} from '@nestjs/common';
10
import { Request } from 'express';
11
import { User } from 'src/Domain/HumanResource/User/User.entity';
12
import { GetMonthlyFairCalendarQuery } from 'src/Application/FairCalendar/Query/GetMonthlyFairCalendarQuery';
13
import { IQueryBus } from 'src/Application/IQueryBus';
14
import { IsAuthenticatedGuard } from 'src/Infrastructure/HumanResource/User/Security/IsAuthenticatedGuard';
15
import { WithName } from 'src/Infrastructure/Common/ExtendedRouting/WithName';
16
import { FairCalendarControllerDTO } from '../DTO/FairCalendarControllerDTO';
17
import { ITranslator } from 'src/Infrastructure/Translations/ITranslator';
18
import { minutesToHours } from 'src/Infrastructure/Common/Utils/dateUtils';
19
import { LoggedUser } from 'src/Infrastructure/HumanResource/User/Decorator/LoggedUser';
20
import { UserView } from 'src/Application/HumanResource/User/View/UserView';
21
import { GetUsersQuery } from 'src/Application/HumanResource/User/Query/GetUsersQuery';
22
import { FairCalendarView } from 'src/Application/FairCalendar/View/FairCalendarView';
23
import { FairCalendarOverviewFactory } from 'src/Domain/FairCalendar/FairCalendarOverviewFactory';
24
import { FairCalendarOverviewTableFactory } from '../Table/FairCalendarOverviewTableFactory';
25
import { IDateUtils } from 'src/Application/IDateUtils';
26
import { ArrayUtils } from 'src/Infrastructure/Common/Utils/ArrayUtils';
27
import { RouteNameResolver } from 'src/Infrastructure/Common/ExtendedRouting/RouteNameResolver';
28
29
@Controller('app/faircalendar')
30
@UseGuards(IsAuthenticatedGuard)
31
export class FairCalendarController {
32
  constructor(
33
    @Inject('IQueryBus')
34
    private readonly queryBus: IQueryBus,
35
    @Inject('ITranslator')
36
    private readonly translator: ITranslator,
37
    @Inject('IDateUtils')
38
    private readonly dateUtils: IDateUtils,
39
    private overviewFactory: FairCalendarOverviewFactory,
40
    private overviewTableFactory: FairCalendarOverviewTableFactory,
41
    private readonly resolver: RouteNameResolver
42
  ) {}
43
44
  @Get()
45
  @WithName('faircalendar_index')
46
  @Render('pages/faircalendar/index.njk')
47
  public async get(
48
    @Query() dto: FairCalendarControllerDTO,
49
    @LoggedUser() user: User,
50
    @Req() req: Request
51
  ) {
52
    let date = new Date();
53
54
    if (dto.year !== undefined && dto.month !== undefined) {
55
      date = new Date(dto.year, dto.month - 1, 15);
56
    }
57
58
    const userId = dto.userId ? dto.userId : user['id'];
59
60
    const users: UserView[] = await this.queryBus.execute(
61
      new GetUsersQuery(false, true)
62
    );
63
64
    const events: FairCalendarView[] = await this.queryBus.execute(
65
      new GetMonthlyFairCalendarQuery(date, userId)
66
    );
67
68
    const overview = await this.overviewFactory.create(events);
69
    const overviewTable = this.overviewTableFactory.create(overview);
70
71
    const fullCalendarEvents = events.map(event => {
72
      let title = `${minutesToHours(event.time)} - `;
73
74
      const fcEventType = event.type.startsWith('leave_')
75
        ? 'leave'
76
        : event.type;
77
78
      if (fcEventType === 'mission' && event.task && event.project) {
79
        title += `${event.project.name} (${event.task.name})`;
80
      } else if (fcEventType === 'leave') {
81
        title += `${this.translator.translate('leaves-type-value', {
82
          type: event.type.slice(6)
83
        })}`;
84
      } else {
85
        title += `${this.translator.translate('faircalendar-type-option', {
86
          type: event.type
87
        })}`;
88
      }
89
90
      const extendedProps: Record<string, any> = {
91
        summary: event.summary
92
      };
93
94
      if (event.id) {
95
        extendedProps.url = this.resolver.resolve('faircalendar_events_edit', {
96
          id: event.id
97
        });
98
      }
99
100
      return {
101
        // See: https://fullcalendar.io/docs/event-object
102
        id: event.id,
103
        type: fcEventType,
104
        start: event.date,
105
        end: event.date,
106
        title,
107
        extendedProps,
108
        textColor: `var(--event-${fcEventType}-text)`,
109
        backgroundColor: `var(--event-${fcEventType}-background)`,
110
        borderColor: `var(--event-${fcEventType}-border)`
111
      };
112
    });
113
114
    const eventsByStartDate = ArrayUtils.groupBy(
115
      fullCalendarEvents,
116
      event => event.start
117
    );
118
119
    const listViewDays = this.dateUtils.getWeekDaysOfMonth(date).map(day => {
120
      return [
121
        day,
122
        eventsByStartDate[this.dateUtils.format(day, 'yyyy-MM-dd')] || []
123
      ];
124
    });
125
126
    return {
127
      users,
128
      overviewTable,
129
      fullCalendarEvents,
130
      date,
131
      currentMonth: date.getMonth() + 1,
132
      currentYear: date.getFullYear(),
133
      userId,
134
      viewName: req.cookies.faircalendar_view,
135
      listViewDays,
136
      isCalendarOfLoggedUser: userId === user.getId()
137
    };
138
  }
139
}
140